using B.Z.BasicData.Infrastructure;
using B.Z.Inventory.API.Read.Application.Command;
using B.Z.Inventory.API.Read.DTO;
using B.Z.Inventory.Domain;
using B.Z.Inventory.ErrorCode;
using MediatR;
using Microsoft.EntityFrameworkCore;

namespace B.Z.Inventory.API.Read.Application.CommandHandler
{
    /// <summary>
    /// 出入库排名查询命令处理器
    /// </summary>
    public class InOutboundRankingCommandHandler : IRequestHandler<InOutboundRankingCommand, APIResult<InOutboundRankingDto>>
    {
        private readonly IBaseRepository<T_IntOutStore> intOutStoreRepository;
        private readonly IBaseRepository<T_Goods> goodsRepository;
        private readonly ILogger<InOutboundRankingCommandHandler> logger;

        public InOutboundRankingCommandHandler(
            IBaseRepository<T_IntOutStore> intOutStoreRepository,
            IBaseRepository<T_Goods> goodsRepository,
            ILogger<InOutboundRankingCommandHandler> logger)
        {
            this.intOutStoreRepository = intOutStoreRepository;
            this.goodsRepository = goodsRepository;
            this.logger = logger;
        }

        public Task<APIResult<InOutboundRankingDto>> Handle(InOutboundRankingCommand request, CancellationToken cancellationToken)
        {
            APIResult<InOutboundRankingDto> result = new APIResult<InOutboundRankingDto>();
            result.Code = APIEnums.ok;

            try
            {
                // 获取出入库记录
                var query = intOutStoreRepository.GetAll()
                    .AsNoTracking()
                    .Where(x => !x.IsDelete && x.IsIntOrOut == request.IsInbound);

                // 应用时间筛选
                if (request.StartDate.HasValue)
                {
                    query = query.Where(x => x.IntOutStoreTime >= request.StartDate.Value);
                }

                if (request.EndDate.HasValue)
                {
                    query = query.Where(x => x.IntOutStoreTime <= request.EndDate.Value);
                }

                // 应用仓库筛选
                if (request.StoreId.HasValue)
                {
                    query = query.Where(x => x.StoreId == request.StoreId.Value);
                }

                // 按商品分组统计
                var rankingData = query
                    .GroupBy(x => x.GoodsIds) // 注意：这里假设GoodsIds是单个商品ID，实际可能需要解析
                    .Select(g => new
                    {
                        GoodsIdStr = g.Key,
                        TotalQuantity = g.Sum(x => x.Count),
                        OperationCount = g.Count()
                    })
                    .ToList();

                // 解析商品ID并获取商品信息
                var rankings = new List<GoodsInOutRanking>();
                foreach (var item in rankingData)
                {
                    if (int.TryParse(item.GoodsIdStr, out int goodsId))
                    {
                        var goods = goodsRepository.GetAll()
                            .AsNoTracking()
                            .FirstOrDefault(x => x.Id == goodsId && !x.IsDelete);

                        if (goods != null)
                        {
                            rankings.Add(new GoodsInOutRanking
                            {
                                GoodsId = goodsId,
                                GoodsName = goods.GoodsName,
                                GoodsNumber = goods.GoodsNumber,
                                TotalQuantity = item.TotalQuantity,
                                OperationCount = item.OperationCount,
                                IsInbound = request.IsInbound
                            });
                        }
                    }
                }

                // 按数量排序并设置排名
                rankings = rankings
                    .OrderByDescending(x => x.TotalQuantity)
                    .Take(request.TopCount)
                    .ToList();

                for (int i = 0; i < rankings.Count; i++)
                {
                    rankings[i].Rank = i + 1;
                }

                result.Data = new InOutboundRankingDto
                {
                    StatisticsType = request.IsInbound ? "入库排名" : "出库排名",
                    StartDate = request.StartDate,
                    EndDate = request.EndDate,
                    Rankings = rankings
                };

                logger.LogInformation($"成功获取{(request.IsInbound ? "入库" : "出库")}排名，共{rankings.Count}条记录");
            }
            catch (Exception ex)
            {
                logger.LogError(ex, $"获取{(request.IsInbound ? "入库" : "出库")}排名时发生错误");
                result.Code = APIEnums.fail;
                result.Message = $"获取{(request.IsInbound ? "入库" : "出库")}排名失败";
            }

            return Task.FromResult(result);
        }
    }
}